package com.lollipop.synthential.concurrency.thread;

/**
 * @Author: J.K
 * @Date: 2020-07-03 16:39
 * @Description: 测试volatile关键字的内存可见性作用
 */
public class ThreadVolatile {
    /**
     * PS：解决i++非原子性操作的问题-->单纯的使用volatile关键字去定义count变量是无效的，
     * 原因是当变量的值由自身的上一个值决定时，如i++,i=i+1等，volatile将失效，
     * 只有当【变量的值和自身上一个值无关】时对该变量的操作才是原子级别的，如i=j+1
     */
    private static volatile boolean flag = false;

    public static void main(String[] args) throws Exception {

        notifyThreadWithVolatile();

    }

    /**
     * 计算i++，当i==5时，通知线程B
     *
     * @throws Exception
     */
    private static void notifyThreadWithVolatile() throws Exception {
        Thread tha = new Thread("线程A") {
            @Override
            public void run() {
                for (int i = 0; i < 10; i++) {
                    if (i == 5) {
                        flag = true;
                        try {
                            Thread.sleep(500L);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                        break;
                    }
                    System.out.println(Thread.currentThread().getName() + "====" + i);
                }
            }
        };

        Thread thb = new Thread("线程B") {
            @Override
            public void run() {
                while (true) {
                    // 防止伪唤醒 所以使用了while
                    while (flag) {
                        System.out.println(Thread.currentThread().getName() + "收到通知");
                        System.out.println("do something");
                        try {
                            Thread.sleep(500L);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                        return;
                    }

                }
            }
        };

        thb.start();
        Thread.sleep(1000L);
        tha.start();

    }
}

